package com.querie.util;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import com.querie.dao.DAOFactory;
import com.querie.dao.QueryDAO;
import com.querie.dao.QuerylogDAOImpl;
import com.querie.model.beans.PrecisionRecallStatistics;
import com.querie.model.beans.Query;

public class MetricsCalc {

	private static HashMap<Long, Double> precisions = new HashMap<Long, Double>();
	private static HashMap<Long, Double> recalls = new HashMap<Long, Double>();
	private static double averagePrecision = 0.0;
	private static double averageRecall  = 0.0;
	private static double maxPrecision = 0.0;
	private static double maxRecall = 0.0;
	
	public static void calculatePrecisionAndRecall(List<Long> queryIds, long queryId)
	{
		maxPrecision = 0.0;
		maxRecall = 0.0;
		try {
			QueryDAO qDAO = DAOFactory.getQueryDAO();
			Query q = qDAO.load(queryId);
			List<Long> unSeenQueryFragList = getFragmentList(q.getQueryfragmentimportance());
			double precisionSum = 0;
			double recallSum = 0;	
			for (Long qId: queryIds)
			{
				List<Long> recommendedQueryFragList = getFragmentList(qDAO.load(qId).getQueryfragmentimportance());
				int intersectionCount = 0;
				
				for (Long uQueryFrag : unSeenQueryFragList)
				{
					if (recommendedQueryFragList.contains(uQueryFrag))
					{
						intersectionCount++;
					}
				}
				double precision = (1.0*intersectionCount)/(1.0*recommendedQueryFragList.size());
				double recall = (1.0*intersectionCount)/(1.0*unSeenQueryFragList.size());
				

				if (precision > maxPrecision)
				{
					maxPrecision = precision;
				}
				
				if (recall > maxRecall)
				{
					maxRecall = recall;
				}
				precisions.put(qId, precision);
				recalls.put(qId, recall);
				precisionSum+=precision;
				recallSum+=recall;
			}
			
			
			averagePrecision=precisionSum/queryIds.size();
			averageRecall=recallSum/queryIds.size();
			
			if (averagePrecision <= 0.0 || averageRecall == 0.0)
			{
				System.out.println("Caught");
				// Unseen queries
				
				// Recommended query
				// Unseen query fragment list
				// recommended query fragment list
			}
			
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		
	}
	
	public static List<Long> getFragmentList(String fragmentStr)
	{
		String[] fragmentArr = fragmentStr.split("::");
		List<Long> fragmentList = new ArrayList<Long>();
		for(String str: fragmentArr)
		{
			fragmentList.add(Long.parseLong(str.split(",")[0]));
		}
		return fragmentList;
	}

	public static HashMap<Long, Double> getPrecisions() {
		return precisions;
	}

	public static void setPrecisions(HashMap<Long, Double> precisions) {
		MetricsCalc.precisions = precisions;
	}

	public static HashMap<Long, Double> getRecalls() {
		return recalls;
	}

	public static void setRecalls(HashMap<Long, Double> recalls) {
		MetricsCalc.recalls = recalls;
	}

	public static double getAveragePrecision() {
		return averagePrecision;
	}

	public static void setAveragePrecision(double averagePrecision) {
		MetricsCalc.averagePrecision = averagePrecision;
	}

	public static double getAverageRecall() {
		return averageRecall;
	}

	public static void setAverageRecall(double averageRecall) {
		MetricsCalc.averageRecall = averageRecall;
	}

	public static double getMaxPrecision() {
		return maxPrecision;
	}

	public static double getMaxRecall() {
		return maxRecall;
	}
}
